<?php



class Dims
{
    public $height;
    public $width;
    
    public function __construct($height, $width)
    {
        $this->height = $height;
        $this->width = $width;    
    }    
}

class Site
{
    public $thumbnail_size;
    public $database;
    private $photo_cache = null;
    
    public function __construct()
    {
        $this->thumbnail_size = new Dims(120, 160);
        $this->database = new Database();
        $this->photo_cache = new PhotoCache();
    }
    
    public static function getResizeURL($source_id, $id, Dims $dims)
    {
        return "index.php?action=resize&source=$source_id&id=".urlencode($id)."&w={$dims->width}&h={$dims->height}";
    }
    
    public static function getURL($action, $source_id, $id)
    {
        return "index.php?action=$action&source=$source_id&id=".urlencode($id);
    }
    
    public function getPhotoCache()
    {
        return $this->photo_cache;
    }
}

class MovieViewer
{
    private $path;
    
    public function __construct(UriMovie_I $movie)
    {
        $this->path = $movie->getPath();
    }
    
    /**
     * Gets a snapshot of a movie.
     * @returns GD Image Object
     */
    public function getSnapshotImage(Dims $dims)
    {
        $extension = "ffmpeg";

        // load extension
        if(!extension_loaded($extension) && function_exists('dl')) {
            $extension_soname = $extension . "." . PHP_SHLIB_SUFFIX;
            $extension_fullname = PHP_EXTENSION_DIR . "/" . $extension_soname;
            dl($extension_soname);
        }
        
        if (!class_exists('ffmpeg_movie', FALSE) || !method_exists('ffmpeg_movie', 'getFrame')) {
            return imagecreatefrompng("images/video-x-generic.png");
        }
        
        $movie = new ffmpeg_movie($this->path, FALSE);
        $frame = $movie->getFrame();
        return $frame->toGDImage();
    }
}

class Database
{
    
    public function __construct()
    {
        
    }
    
    public function works()
    {
        return false;
    }

    public function setValue($key, $name, $value)
    {
        return;
    }
    
    public function getValue($key, $name)
    {
        return false;
    }
}

class PhotoCache
{
    public function __construct()
    {
    
    }
   
    public function works()
    {
         $works = (defined('PHOTO_CACHE_PATH') 
                     && is_dir(PHOTO_CACHE_PATH)  
                     && is_writeable(PHOTO_CACHE_PATH));
         error_log('Photo cache works: '.$works);
         return $works;
    }
    
    public function save($source_id, $photo_id, $binary_data, Dims $size)
    {
         $name = $this->createName($source_id, $photo_id, $size);
         $path = PHOTO_CACHE_PATH . '/' . $name;
         file_put_contents($path, $binary_data);
    }
    
    public function saveImage($source_id, $photo_id, &$photo, Dims $size)
    {
         $name = $this->createName($source_id, $photo_id, $size);
         $path = PHOTO_CACHE_PATH . '/' . $name;
         imagejpeg($photo, $path);
    }
    
    public function getData($source_id, $photo_id, Dims $size, $last_modified)
    {
        $name = $this->createName($source_id, $photo_id, $size);
        $path = PHOTO_CACHE_PATH.'/'.$name;
        $stats = @stat($path);
        if (!isset($stats) || ($last_modified > $stats['mtime'])) {
            unlink($path);
            return false; 
        }
        return file_get_contents($path);
    }
    
    private function createName($source_id, $photo_id, Dims $size)
    {
        $bad_chars = array(' ', '&', "/", "\\");
        $good_chars = array('_','_','_','_');
        $pid = str_replace($bad_chars, $good_chars, $photo_id);
        return "$source_id-$pid-w{$size->width}-h{$size->height}.jpeg";
    }
}